package com.marktotop.service.impl;

import com.marktotop.converter.MenuConverter;
import com.marktotop.entity.system.Menu;
import com.marktotop.enums.UserTypeEnum;
import com.marktotop.error.SystemCodeEnum;
import com.marktotop.error.SystemException;
import com.marktotop.mapper.MenuMapper;
import com.marktotop.service.IMenuService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.marktotop.utils.MenuTreeBuilder;
import com.marktotop.vo.system.ActiveUserVO;
import com.marktotop.vo.system.MenuNodeVO;
import com.marktotop.vo.system.MenuVO;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * <p>
 * 菜单表 服务实现类
 * </p>
 *
 * @author MarkToTop
 * @since 2021-07-12
 */
@Service
public class MenuServiceImpl extends ServiceImpl<MenuMapper, Menu> implements IMenuService {

    @Autowired
    private MenuMapper menuMapper;

    @Override
    public List<MenuNodeVO> findMenu() {
        List<Menu> menus=null;
        List<MenuNodeVO> menuNodeVOS=new ArrayList<>();
        ActiveUserVO activeUser = (ActiveUserVO) SecurityUtils.getSubject().getPrincipal();
        if(activeUser.getUser().getType() == UserTypeEnum.SYSTEM_ADMIN.getTypeCode()){
            //超级管理员 - 全部菜单
            menus = menuMapper.selectList(null);
        }else if(activeUser.getUser().getType() == UserTypeEnum.SYSTEM_USER.getTypeCode()){
            //普通系统用户 - 根据激活用户信息 查询 部分菜单
            menus= activeUser.getMenus();
        }

        if(!CollectionUtils.isEmpty(menus)){
            // 如果集合不为空，转化为 菜单树
            menuNodeVOS= MenuConverter.converterToMenuNodeVO(menus);
        }
        //构建树形菜单
        return MenuTreeBuilder.build(menuNodeVOS);
    }


    /**
     * 加载菜单树（按钮和菜单）
     *
     * @return
     */
    @Override
    public List<MenuNodeVO> findMenuTree() {
        List<Menu> menus = menuMapper.selectList(null);
        List<MenuNodeVO> menuNodeVOS = MenuConverter.converterToALLMenuNodeVO(menus);
        return MenuTreeBuilder.build(menuNodeVOS);
    }


    /**
     * 获取展开项
     *
     * @return
     */
    @Override
    public List<Long> findOpenIds() {
        List<Long> ids=new ArrayList<>();
        List<Menu> menus = menuMapper.selectList(null);
        if(!CollectionUtils.isEmpty(menus)){
            for (Menu menu : menus) {
                if(menu.getOpen()==1){
                    ids.add(menu.getId());
                }
            }
        }
        return ids;
    }


    /**
     * 新增菜单/按钮
     *
     * @param menuVO
     * @return
     */
    @Override
    public Menu addMenus(MenuVO menuVO) {
        Menu menu = new Menu();
        BeanUtils.copyProperties(menuVO,menu);
        menu.setCreateTime(new Date());
        menu.setModifiedTime(new Date());
        menu.setAvailable(menuVO.isDisabled()?0:1);
        menuMapper.insert(menu);
        return menu;
    }


    /**
     * 编辑菜单详情
     *
     * @param id
     * @return
     * @throws SystemException
     */
    @Override
    public MenuVO editMenu(Long id) throws SystemException {
        Menu menu = menuMapper.selectById(id);
        if(null == menu){
            throw new SystemException(SystemCodeEnum.PARAMETER_ERROR,"该编辑的菜单不存在");
        }
        return MenuConverter.converterToMenuVO(menu);
    }


    /**
     * 更新菜单
     * @param id
     * @param menuVO
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateMenu(Long id, MenuVO menuVO) throws SystemException {
        Menu dbMenu = menuMapper.selectById(id);
        if(null == dbMenu){
            throw new SystemException(SystemCodeEnum.PARAMETER_ERROR,"要更新的菜单不存在");
        }
        Menu menu = new Menu();
        BeanUtils.copyProperties(menuVO,menu);
        menu.setId(id);
        menu.setAvailable(menuVO.isDisabled() ? 0 : 1 );
        menu.setModifiedTime(new Date());
        menuMapper.updateById(menu);
    }
}
